﻿using System;
using System.Collections.Generic;
using System.Text;

using BeIT.MemCached;
using Obsidian.Config;
using Obsidian.Edm;
using Obsidian.Utils;
using Obsidian.Runtime;

namespace Obsidian.Data
{
    public class MemCached
    {

        private static string defautlName = null;

        public static void Prepare()
        {
            if(MemcachedConfig.CheckForChanged())
            {
                ICollection<MemcachedConfig.ClientInfo> clientList = MemcachedConfig.GetClientList();
                foreach (MemcachedConfig.ClientInfo client in clientList)
                {
                    MemcachedClient.Setup(client.Name, client.Server.Split(','));
                }
                defautlName = MemcachedConfig.DefaultName;
            }
        }

        private static MemcachedClient DefaultClient
        {
            get
            {
                Prepare();
                if (String.IsNullOrEmpty(defautlName))
                    throw new Exception("未设置默认Memcached配置");
                return GetClient(defautlName);
            }
        }


        private static MemcachedClient GetClient(string name)
        {
            MemcachedClient client = MemcachedClient.GetInstance(defautlName);
            client.MinPoolSize = 1;
            client.MaxPoolSize = 5;
            return client;
        }


        public static void Set(string key, string val)
        {
            Set(key, val, -1);
        }

        public static void Set(string key, string val, int validTime)
        {
            MemcachedClient client = DefaultClient;
            if (validTime > 0)
                client.Set(key, val, new TimeSpan(0, 0, validTime));
            else
                client.Set(key, val);
        }

        public static void Set<T>(string key, T value) where T : IModel, new()
        {
            Set<T>(key, value, -1);
        }

        public static void Set<T>(string key, T value, int validTime) where T : IModel, new()
        {
            MemcachedClient client = DefaultClient;
            string k = typeof(T).Name;
            k = k + "_" + key;
            string jsonString = ModelUtil.ToJsonString(value);
            if (validTime > 0)
                client.Set(k, jsonString, new TimeSpan(0, 0, validTime));
            else
                client.Set(k, jsonString);
        }

        public static string Get(string key)
        {
            MemcachedClient client = DefaultClient;
            object val = client.Get(key);
            if (val == null)
                return null;
            return Convert.ToString(val);
        }

        public static T Get<T>(string key) where T : IModel, new()
        {
            MemcachedClient client = DefaultClient;
            string k = typeof(T).Name;
            k = k + "_" + key;
            object val = client.Get(k);
            if (val == null)
                return default(T);
            string jsonString = Convert.ToString(val);
            T o = ModelUtil.ToModel<T>(jsonString);
            return o;
        }

        public static bool Exists<T>(string key) where T : IModel, new()
        {
            return Get<T>(key) != null;
        }

        public static bool Delete(string key)
        {
            MemcachedClient client = DefaultClient;
            return client.Delete(key);
        }

        public static void Delete<T>(string key) where T : IModel, new()
        {
            MemcachedClient client = DefaultClient;
            string k = typeof(T).Name;
            k = k + "_" + key;
            client.Delete(k);
        }
    }
}
